//===----------------------------------------------------------------------===//
//
// This source file is part of the Soto for AWS open source project
//
// Copyright (c) 2017-2022 the Soto project authors
// Licensed under Apache License v2.0
//
// See LICENSE.txt for license information
// See CONTRIBUTORS.txt for the list of Soto project authors
//
// SPDX-License-Identifier: Apache-2.0
//
//===----------------------------------------------------------------------===//

// THIS FILE IS AUTOMATICALLY GENERATED by https://github.com/soto-project/soto-codegenerator.
// DO NOT EDIT.

import Foundation
import SotoCore

extension Keyspaces {
    // MARK: Enums

    public enum EncryptionType: String, CustomStringConvertible, Codable, _SotoSendable {
        case awsOwnedKmsKey = "AWS_OWNED_KMS_KEY"
        case customerManagedKmsKey = "CUSTOMER_MANAGED_KMS_KEY"
        public var description: String { return self.rawValue }
    }

    public enum PointInTimeRecoveryStatus: String, CustomStringConvertible, Codable, _SotoSendable {
        case disabled = "DISABLED"
        case enabled = "ENABLED"
        public var description: String { return self.rawValue }
    }

    public enum SortOrder: String, CustomStringConvertible, Codable, _SotoSendable {
        case asc = "ASC"
        case desc = "DESC"
        public var description: String { return self.rawValue }
    }

    public enum TableStatus: String, CustomStringConvertible, Codable, _SotoSendable {
        case active = "ACTIVE"
        case creating = "CREATING"
        case deleted = "DELETED"
        case deleting = "DELETING"
        case inaccessibleEncryptionCredentials = "INACCESSIBLE_ENCRYPTION_CREDENTIALS"
        case restoring = "RESTORING"
        case updating = "UPDATING"
        public var description: String { return self.rawValue }
    }

    public enum ThroughputMode: String, CustomStringConvertible, Codable, _SotoSendable {
        case payPerRequest = "PAY_PER_REQUEST"
        case provisioned = "PROVISIONED"
        public var description: String { return self.rawValue }
    }

    public enum TimeToLiveStatus: String, CustomStringConvertible, Codable, _SotoSendable {
        case enabled = "ENABLED"
        public var description: String { return self.rawValue }
    }

    // MARK: Shapes

    public struct CapacitySpecification: AWSEncodableShape {
        /// The throughput capacity specified for read operations defined in read capacity units  (RCUs).
        public let readCapacityUnits: Int64?
        /// The read/write throughput capacity mode for a table. The options are: • throughputMode:PAY_PER_REQUEST and  • throughputMode:PROVISIONED - Provisioned capacity mode requires readCapacityUnits and writeCapacityUnits as input. The default is throughput_mode:PAY_PER_REQUEST. For more information, see Read/write capacity modes in the Amazon Keyspaces Developer Guide.
        public let throughputMode: ThroughputMode
        /// The throughput capacity specified for write operations defined in write capacity units  (WCUs).
        public let writeCapacityUnits: Int64?

        public init(readCapacityUnits: Int64? = nil, throughputMode: ThroughputMode, writeCapacityUnits: Int64? = nil) {
            self.readCapacityUnits = readCapacityUnits
            self.throughputMode = throughputMode
            self.writeCapacityUnits = writeCapacityUnits
        }

        public func validate(name: String) throws {
            try self.validate(self.readCapacityUnits, name: "readCapacityUnits", parent: name, min: 1)
            try self.validate(self.writeCapacityUnits, name: "writeCapacityUnits", parent: name, min: 1)
        }

        private enum CodingKeys: String, CodingKey {
            case readCapacityUnits
            case throughputMode
            case writeCapacityUnits
        }
    }

    public struct CapacitySpecificationSummary: AWSDecodableShape {
        /// The timestamp of the last operation that changed the provisioned throughput capacity of a table.
        public let lastUpdateToPayPerRequestTimestamp: Date?
        /// The throughput capacity specified for read operations defined in read capacity units  (RCUs).
        public let readCapacityUnits: Int64?
        /// The read/write throughput capacity mode for a table. The options are: • throughputMode:PAY_PER_REQUEST and  • throughputMode:PROVISIONED - Provisioned capacity mode requires readCapacityUnits and writeCapacityUnits as input.  The default is throughput_mode:PAY_PER_REQUEST. For more information, see Read/write capacity modes in the Amazon Keyspaces Developer Guide.
        public let throughputMode: ThroughputMode
        /// The throughput capacity specified for write operations defined in write capacity units  (WCUs).
        public let writeCapacityUnits: Int64?

        public init(lastUpdateToPayPerRequestTimestamp: Date? = nil, readCapacityUnits: Int64? = nil, throughputMode: ThroughputMode, writeCapacityUnits: Int64? = nil) {
            self.lastUpdateToPayPerRequestTimestamp = lastUpdateToPayPerRequestTimestamp
            self.readCapacityUnits = readCapacityUnits
            self.throughputMode = throughputMode
            self.writeCapacityUnits = writeCapacityUnits
        }

        private enum CodingKeys: String, CodingKey {
            case lastUpdateToPayPerRequestTimestamp
            case readCapacityUnits
            case throughputMode
            case writeCapacityUnits
        }
    }

    public struct ClusteringKey: AWSEncodableShape & AWSDecodableShape {
        /// The name(s) of the clustering column(s).
        public let name: String
        /// Sets the ascendant (ASC) or descendant (DESC) order modifier.
        public let orderBy: SortOrder

        public init(name: String, orderBy: SortOrder) {
            self.name = name
            self.orderBy = orderBy
        }

        private enum CodingKeys: String, CodingKey {
            case name
            case orderBy
        }
    }

    public struct ColumnDefinition: AWSEncodableShape & AWSDecodableShape {
        /// The name of the column.
        public let name: String
        /// The data type of the column. For a list of available data types, see Data types in the Amazon Keyspaces Developer Guide.
        public let type: String

        public init(name: String, type: String) {
            self.name = name
            self.type = type
        }

        private enum CodingKeys: String, CodingKey {
            case name
            case type
        }
    }

    public struct Comment: AWSEncodableShape & AWSDecodableShape {
        /// An optional description of the table.
        public let message: String

        public init(message: String) {
            self.message = message
        }

        private enum CodingKeys: String, CodingKey {
            case message
        }
    }

    public struct CreateKeyspaceRequest: AWSEncodableShape {
        /// The name of the keyspace to be created.
        public let keyspaceName: String
        /// A list of key-value pair tags to be attached to the keyspace. For more information, see Adding tags and labels to Amazon Keyspaces resources in the Amazon Keyspaces Developer Guide.
        public let tags: [Tag]?

        public init(keyspaceName: String, tags: [Tag]? = nil) {
            self.keyspaceName = keyspaceName
            self.tags = tags
        }

        public func validate(name: String) throws {
            try self.validate(self.keyspaceName, name: "keyspaceName", parent: name, max: 48)
            try self.validate(self.keyspaceName, name: "keyspaceName", parent: name, min: 1)
            try self.validate(self.keyspaceName, name: "keyspaceName", parent: name, pattern: "^[a-zA-Z0-9][a-zA-Z0-9_]{1,47}$")
            try self.tags?.forEach {
                try $0.validate(name: "\(name).tags[]")
            }
            try self.validate(self.tags, name: "tags", parent: name, max: 60)
            try self.validate(self.tags, name: "tags", parent: name, min: 1)
        }

        private enum CodingKeys: String, CodingKey {
            case keyspaceName
            case tags
        }
    }

    public struct CreateKeyspaceResponse: AWSDecodableShape {
        /// The unique identifier of the keyspace in the format of an Amazon Resource Name (ARN).
        public let resourceArn: String

        public init(resourceArn: String) {
            self.resourceArn = resourceArn
        }

        private enum CodingKeys: String, CodingKey {
            case resourceArn
        }
    }

    public struct CreateTableRequest: AWSEncodableShape {
        /// Specifies the read/write throughput capacity mode for the table. The options are: • throughputMode:PAY_PER_REQUEST and  • throughputMode:PROVISIONED - Provisioned capacity mode requires readCapacityUnits and writeCapacityUnits as input. The default is throughput_mode:PAY_PER_REQUEST. For more information, see Read/write capacity modes in the Amazon Keyspaces Developer Guide.
        public let capacitySpecification: CapacitySpecification?
        /// This parameter allows to enter a description of the table.
        public let comment: Comment?
        /// The default Time to Live setting in seconds for the table. For more information, see Setting the default TTL value for a table in the Amazon Keyspaces Developer Guide.
        public let defaultTimeToLive: Int?
        /// Specifies how the encryption key for encryption at rest is managed for the table.   You can choose one of the following KMS key (KMS key): • type:AWS_OWNED_KMS_KEY - This key is owned by Amazon Keyspaces.     • type:CUSTOMER_MANAGED_KMS_KEY - This key is stored in your account and is created, owned, and managed by you.  This option  requires the kms_key_identifier of the KMS key in Amazon Resource Name (ARN) format as input. The default is type:AWS_OWNED_KMS_KEY.  For more information, see Encryption at rest in the Amazon Keyspaces Developer Guide.
        public let encryptionSpecification: EncryptionSpecification?
        /// The name of the keyspace that the table is going to be created in.
        public let keyspaceName: String
        /// Specifies if pointInTimeRecovery is enabled or disabled for the table. The options are: • ENABLED  • DISABLED  If it's not specified, the  default is DISABLED. For more information, see Point-in-time recovery in the Amazon Keyspaces Developer Guide.
        public let pointInTimeRecovery: PointInTimeRecovery?
        /// The schemaDefinition consists of the following parameters. For each column to be created: • name  -  The name of the column. • type  -  An Amazon Keyspaces data type. For more information, see Data types in the Amazon Keyspaces Developer Guide. The primary key of the table consists of the following columns: • partitionKeys - The partition key can be a single column, or it can be a compound value composed of two or more columns. The partition key portion of the primary key is required and determines how Amazon Keyspaces stores your data. • name - The name of each partition key column. • clusteringKeys - The optional clustering column portion of your primary key determines how the data is clustered and sorted within each partition. • name - The name of the clustering column.  • orderBy - Sets the ascendant (ASC) or descendant (DESC) order modifier. To define a column as static use staticColumns  -  Static columns store values that are shared by all rows in the same partition: • name  -  The name of the column. • type  -  An Amazon Keyspaces data type.
        public let schemaDefinition: SchemaDefinition
        /// The name of the table.
        public let tableName: String
        /// A list of key-value pair tags to be attached to the resource.  For more information, see Adding tags and labels to Amazon Keyspaces resources in the Amazon Keyspaces Developer Guide.
        public let tags: [Tag]?
        /// Enables Time to Live custom settings for the table. The options are: • status:enabled  • status:disabled  The default is status:disabled. After ttl is enabled, you can't disable it for the table. For more information, see Expiring data by using Amazon Keyspaces Time to Live (TTL) in the Amazon Keyspaces Developer Guide.
        public let ttl: TimeToLive?

        public init(capacitySpecification: CapacitySpecification? = nil, comment: Comment? = nil, defaultTimeToLive: Int? = nil, encryptionSpecification: EncryptionSpecification? = nil, keyspaceName: String, pointInTimeRecovery: PointInTimeRecovery? = nil, schemaDefinition: SchemaDefinition, tableName: String, tags: [Tag]? = nil, ttl: TimeToLive? = nil) {
            self.capacitySpecification = capacitySpecification
            self.comment = comment
            self.defaultTimeToLive = defaultTimeToLive
            self.encryptionSpecification = encryptionSpecification
            self.keyspaceName = keyspaceName
            self.pointInTimeRecovery = pointInTimeRecovery
            self.schemaDefinition = schemaDefinition
            self.tableName = tableName
            self.tags = tags
            self.ttl = ttl
        }

        public func validate(name: String) throws {
            try self.capacitySpecification?.validate(name: "\(name).capacitySpecification")
            try self.validate(self.defaultTimeToLive, name: "defaultTimeToLive", parent: name, max: 630_720_000)
            try self.validate(self.defaultTimeToLive, name: "defaultTimeToLive", parent: name, min: 1)
            try self.encryptionSpecification?.validate(name: "\(name).encryptionSpecification")
            try self.validate(self.keyspaceName, name: "keyspaceName", parent: name, max: 48)
            try self.validate(self.keyspaceName, name: "keyspaceName", parent: name, min: 1)
            try self.validate(self.keyspaceName, name: "keyspaceName", parent: name, pattern: "^[a-zA-Z0-9][a-zA-Z0-9_]{1,47}$")
            try self.schemaDefinition.validate(name: "\(name).schemaDefinition")
            try self.validate(self.tableName, name: "tableName", parent: name, max: 48)
            try self.validate(self.tableName, name: "tableName", parent: name, min: 1)
            try self.validate(self.tableName, name: "tableName", parent: name, pattern: "^[a-zA-Z0-9][a-zA-Z0-9_]{1,47}$")
            try self.tags?.forEach {
                try $0.validate(name: "\(name).tags[]")
            }
            try self.validate(self.tags, name: "tags", parent: name, max: 60)
            try self.validate(self.tags, name: "tags", parent: name, min: 1)
        }

        private enum CodingKeys: String, CodingKey {
            case capacitySpecification
            case comment
            case defaultTimeToLive
            case encryptionSpecification
            case keyspaceName
            case pointInTimeRecovery
            case schemaDefinition
            case tableName
            case tags
            case ttl
        }
    }

    public struct CreateTableResponse: AWSDecodableShape {
        /// The unique identifier of the table in the format of an Amazon Resource Name (ARN).
        public let resourceArn: String

        public init(resourceArn: String) {
            self.resourceArn = resourceArn
        }

        private enum CodingKeys: String, CodingKey {
            case resourceArn
        }
    }

    public struct DeleteKeyspaceRequest: AWSEncodableShape {
        /// The name of the keyspace to be deleted.
        public let keyspaceName: String

        public init(keyspaceName: String) {
            self.keyspaceName = keyspaceName
        }

        public func validate(name: String) throws {
            try self.validate(self.keyspaceName, name: "keyspaceName", parent: name, max: 48)
            try self.validate(self.keyspaceName, name: "keyspaceName", parent: name, min: 1)
            try self.validate(self.keyspaceName, name: "keyspaceName", parent: name, pattern: "^[a-zA-Z0-9][a-zA-Z0-9_]{1,47}$")
        }

        private enum CodingKeys: String, CodingKey {
            case keyspaceName
        }
    }

    public struct DeleteKeyspaceResponse: AWSDecodableShape {
        public init() {}
    }

    public struct DeleteTableRequest: AWSEncodableShape {
        /// The name of the keyspace of the to be deleted table.
        public let keyspaceName: String
        /// The name of the table to be deleted.
        public let tableName: String

        public init(keyspaceName: String, tableName: String) {
            self.keyspaceName = keyspaceName
            self.tableName = tableName
        }

        public func validate(name: String) throws {
            try self.validate(self.keyspaceName, name: "keyspaceName", parent: name, max: 48)
            try self.validate(self.keyspaceName, name: "keyspaceName", parent: name, min: 1)
            try self.validate(self.keyspaceName, name: "keyspaceName", parent: name, pattern: "^[a-zA-Z0-9][a-zA-Z0-9_]{1,47}$")
            try self.validate(self.tableName, name: "tableName", parent: name, max: 48)
            try self.validate(self.tableName, name: "tableName", parent: name, min: 1)
            try self.validate(self.tableName, name: "tableName", parent: name, pattern: "^[a-zA-Z0-9][a-zA-Z0-9_]{1,47}$")
        }

        private enum CodingKeys: String, CodingKey {
            case keyspaceName
            case tableName
        }
    }

    public struct DeleteTableResponse: AWSDecodableShape {
        public init() {}
    }

    public struct EncryptionSpecification: AWSEncodableShape & AWSDecodableShape {
        /// The Amazon Resource Name (ARN) of the customer managed KMS key, for example kms_key_identifier:ARN.
        public let kmsKeyIdentifier: String?
        /// The encryption option specified for the table. You can choose one of the following KMS keys (KMS keys): • type:AWS_OWNED_KMS_KEY - This key is owned by Amazon Keyspaces.  • type:CUSTOMER_MANAGED_KMS_KEY - This key is stored in your account and is created, owned, and managed by you.  This option  requires the kms_key_identifier of the KMS key in Amazon Resource Name (ARN) format as input.  The default is type:AWS_OWNED_KMS_KEY.  For more information, see Encryption at rest in the Amazon Keyspaces Developer Guide.
        public let type: EncryptionType

        public init(kmsKeyIdentifier: String? = nil, type: EncryptionType) {
            self.kmsKeyIdentifier = kmsKeyIdentifier
            self.type = type
        }

        public func validate(name: String) throws {
            try self.validate(self.kmsKeyIdentifier, name: "kmsKeyIdentifier", parent: name, max: 5096)
            try self.validate(self.kmsKeyIdentifier, name: "kmsKeyIdentifier", parent: name, min: 1)
        }

        private enum CodingKeys: String, CodingKey {
            case kmsKeyIdentifier
            case type
        }
    }

    public struct GetKeyspaceRequest: AWSEncodableShape {
        /// The name of the keyspace.
        public let keyspaceName: String

        public init(keyspaceName: String) {
            self.keyspaceName = keyspaceName
        }

        public func validate(name: String) throws {
            try self.validate(self.keyspaceName, name: "keyspaceName", parent: name, max: 48)
            try self.validate(self.keyspaceName, name: "keyspaceName", parent: name, min: 1)
            try self.validate(self.keyspaceName, name: "keyspaceName", parent: name, pattern: "^[a-zA-Z0-9][a-zA-Z0-9_]{1,47}$")
        }

        private enum CodingKeys: String, CodingKey {
            case keyspaceName
        }
    }

    public struct GetKeyspaceResponse: AWSDecodableShape {
        /// The name of the keyspace.
        public let keyspaceName: String
        /// The ARN of the keyspace.
        public let resourceArn: String

        public init(keyspaceName: String, resourceArn: String) {
            self.keyspaceName = keyspaceName
            self.resourceArn = resourceArn
        }

        private enum CodingKeys: String, CodingKey {
            case keyspaceName
            case resourceArn
        }
    }

    public struct GetTableRequest: AWSEncodableShape {
        /// The name of the keyspace that the table is stored in.
        public let keyspaceName: String
        /// The name of the table.
        public let tableName: String

        public init(keyspaceName: String, tableName: String) {
            self.keyspaceName = keyspaceName
            self.tableName = tableName
        }

        public func validate(name: String) throws {
            try self.validate(self.keyspaceName, name: "keyspaceName", parent: name, max: 48)
            try self.validate(self.keyspaceName, name: "keyspaceName", parent: name, min: 1)
            try self.validate(self.keyspaceName, name: "keyspaceName", parent: name, pattern: "^[a-zA-Z0-9][a-zA-Z0-9_]{1,47}$")
            try self.validate(self.tableName, name: "tableName", parent: name, max: 48)
            try self.validate(self.tableName, name: "tableName", parent: name, min: 1)
            try self.validate(self.tableName, name: "tableName", parent: name, pattern: "^[a-zA-Z0-9][a-zA-Z0-9_]{1,47}$")
        }

        private enum CodingKeys: String, CodingKey {
            case keyspaceName
            case tableName
        }
    }

    public struct GetTableResponse: AWSDecodableShape {
        /// The read/write throughput capacity mode for a table. The options are: • throughputMode:PAY_PER_REQUEST  • throughputMode:PROVISIONED
        public let capacitySpecification: CapacitySpecificationSummary?
        /// The the description of the specified table.
        public let comment: Comment?
        /// The creation timestamp of the specified table.
        public let creationTimestamp: Date?
        /// The default Time to Live settings of the specified table.
        public let defaultTimeToLive: Int?
        /// The encryption settings of the specified table.
        public let encryptionSpecification: EncryptionSpecification?
        /// The name of the keyspace that the specified table is stored in.
        public let keyspaceName: String
        /// The point-in-time recovery status of the specified table.
        public let pointInTimeRecovery: PointInTimeRecoverySummary?
        /// The Amazon Resource Name (ARN) of the specified table.
        public let resourceArn: String
        /// The schema definition of the specified table.
        public let schemaDefinition: SchemaDefinition?
        /// The current status of the specified table.
        public let status: TableStatus?
        /// The name of the specified table.
        public let tableName: String
        /// The custom Time to Live settings of the specified table.
        public let ttl: TimeToLive?

        public init(capacitySpecification: CapacitySpecificationSummary? = nil, comment: Comment? = nil, creationTimestamp: Date? = nil, defaultTimeToLive: Int? = nil, encryptionSpecification: EncryptionSpecification? = nil, keyspaceName: String, pointInTimeRecovery: PointInTimeRecoverySummary? = nil, resourceArn: String, schemaDefinition: SchemaDefinition? = nil, status: TableStatus? = nil, tableName: String, ttl: TimeToLive? = nil) {
            self.capacitySpecification = capacitySpecification
            self.comment = comment
            self.creationTimestamp = creationTimestamp
            self.defaultTimeToLive = defaultTimeToLive
            self.encryptionSpecification = encryptionSpecification
            self.keyspaceName = keyspaceName
            self.pointInTimeRecovery = pointInTimeRecovery
            self.resourceArn = resourceArn
            self.schemaDefinition = schemaDefinition
            self.status = status
            self.tableName = tableName
            self.ttl = ttl
        }

        private enum CodingKeys: String, CodingKey {
            case capacitySpecification
            case comment
            case creationTimestamp
            case defaultTimeToLive
            case encryptionSpecification
            case keyspaceName
            case pointInTimeRecovery
            case resourceArn
            case schemaDefinition
            case status
            case tableName
            case ttl
        }
    }

    public struct KeyspaceSummary: AWSDecodableShape {
        /// The name of the keyspace.
        public let keyspaceName: String
        /// The unique identifier of the keyspace in the format of an Amazon Resource Name (ARN).
        public let resourceArn: String

        public init(keyspaceName: String, resourceArn: String) {
            self.keyspaceName = keyspaceName
            self.resourceArn = resourceArn
        }

        private enum CodingKeys: String, CodingKey {
            case keyspaceName
            case resourceArn
        }
    }

    public struct ListKeyspacesRequest: AWSEncodableShape {
        /// The total number of keyspaces to return in the output. If the total number of keyspaces available  is more than the value specified, a NextToken is provided in the output. To resume pagination,  provide the NextToken value as an argument of a subsequent API invocation.
        public let maxResults: Int?
        /// The pagination token. To resume pagination, provide the NextToken value as argument of a subsequent API invocation.
        public let nextToken: String?

        public init(maxResults: Int? = nil, nextToken: String? = nil) {
            self.maxResults = maxResults
            self.nextToken = nextToken
        }

        public func validate(name: String) throws {
            try self.validate(self.maxResults, name: "maxResults", parent: name, max: 1000)
            try self.validate(self.maxResults, name: "maxResults", parent: name, min: 1)
            try self.validate(self.nextToken, name: "nextToken", parent: name, max: 2048)
            try self.validate(self.nextToken, name: "nextToken", parent: name, min: 1)
        }

        private enum CodingKeys: String, CodingKey {
            case maxResults
            case nextToken
        }
    }

    public struct ListKeyspacesResponse: AWSDecodableShape {
        /// A list of keyspaces.
        public let keyspaces: [KeyspaceSummary]
        /// A token to specify where to start paginating. This is the NextToken from a previously truncated response.
        public let nextToken: String?

        public init(keyspaces: [KeyspaceSummary], nextToken: String? = nil) {
            self.keyspaces = keyspaces
            self.nextToken = nextToken
        }

        private enum CodingKeys: String, CodingKey {
            case keyspaces
            case nextToken
        }
    }

    public struct ListTablesRequest: AWSEncodableShape {
        /// The name of the keyspace.
        public let keyspaceName: String
        /// The total number of tables to return in the output. If the total number of tables available  is more than the value specified, a NextToken is provided in the output. To resume pagination,  provide the NextToken value as an argument of a subsequent API invocation.
        public let maxResults: Int?
        /// The pagination token. To resume pagination, provide the NextToken value as an argument of a subsequent API invocation.
        public let nextToken: String?

        public init(keyspaceName: String, maxResults: Int? = nil, nextToken: String? = nil) {
            self.keyspaceName = keyspaceName
            self.maxResults = maxResults
            self.nextToken = nextToken
        }

        public func validate(name: String) throws {
            try self.validate(self.keyspaceName, name: "keyspaceName", parent: name, max: 48)
            try self.validate(self.keyspaceName, name: "keyspaceName", parent: name, min: 1)
            try self.validate(self.keyspaceName, name: "keyspaceName", parent: name, pattern: "^[a-zA-Z0-9][a-zA-Z0-9_]{1,47}$")
            try self.validate(self.maxResults, name: "maxResults", parent: name, max: 1000)
            try self.validate(self.maxResults, name: "maxResults", parent: name, min: 1)
            try self.validate(self.nextToken, name: "nextToken", parent: name, max: 2048)
            try self.validate(self.nextToken, name: "nextToken", parent: name, min: 1)
        }

        private enum CodingKeys: String, CodingKey {
            case keyspaceName
            case maxResults
            case nextToken
        }
    }

    public struct ListTablesResponse: AWSDecodableShape {
        /// A token to specify where to start paginating. This is the NextToken from a previously truncated response.
        public let nextToken: String?
        /// A list of tables.
        public let tables: [TableSummary]?

        public init(nextToken: String? = nil, tables: [TableSummary]? = nil) {
            self.nextToken = nextToken
            self.tables = tables
        }

        private enum CodingKeys: String, CodingKey {
            case nextToken
            case tables
        }
    }

    public struct ListTagsForResourceRequest: AWSEncodableShape {
        /// The total number of tags to return in the output. If the total number of tags available  is more than the value specified, a NextToken is provided in the output. To resume pagination,  provide the NextToken value as an argument of a subsequent API invocation.
        public let maxResults: Int?
        /// The pagination token. To resume pagination, provide the NextToken value as argument of a subsequent API invocation.
        public let nextToken: String?
        /// The Amazon Resource Name (ARN) of the Amazon Keyspaces resource.
        public let resourceArn: String

        public init(maxResults: Int? = nil, nextToken: String? = nil, resourceArn: String) {
            self.maxResults = maxResults
            self.nextToken = nextToken
            self.resourceArn = resourceArn
        }

        public func validate(name: String) throws {
            try self.validate(self.maxResults, name: "maxResults", parent: name, max: 1000)
            try self.validate(self.maxResults, name: "maxResults", parent: name, min: 1)
            try self.validate(self.nextToken, name: "nextToken", parent: name, max: 2048)
            try self.validate(self.nextToken, name: "nextToken", parent: name, min: 1)
            try self.validate(self.resourceArn, name: "resourceArn", parent: name, max: 1000)
            try self.validate(self.resourceArn, name: "resourceArn", parent: name, min: 20)
            try self.validate(self.resourceArn, name: "resourceArn", parent: name, pattern: "^arn:(aws[a-zA-Z0-9-]*):cassandra:.+")
        }

        private enum CodingKeys: String, CodingKey {
            case maxResults
            case nextToken
            case resourceArn
        }
    }

    public struct ListTagsForResourceResponse: AWSDecodableShape {
        /// A token to specify where to start paginating. This is the NextToken from a previously truncated response.
        public let nextToken: String?
        /// A list of tags.
        public let tags: [Tag]?

        public init(nextToken: String? = nil, tags: [Tag]? = nil) {
            self.nextToken = nextToken
            self.tags = tags
        }

        private enum CodingKeys: String, CodingKey {
            case nextToken
            case tags
        }
    }

    public struct PartitionKey: AWSEncodableShape & AWSDecodableShape {
        /// The name(s) of the partition key column(s).
        public let name: String

        public init(name: String) {
            self.name = name
        }

        private enum CodingKeys: String, CodingKey {
            case name
        }
    }

    public struct PointInTimeRecovery: AWSEncodableShape {
        /// The options are: • ENABLED  • DISABLED
        public let status: PointInTimeRecoveryStatus

        public init(status: PointInTimeRecoveryStatus) {
            self.status = status
        }

        private enum CodingKeys: String, CodingKey {
            case status
        }
    }

    public struct PointInTimeRecoverySummary: AWSDecodableShape {
        /// Specifies the earliest possible restore point of the table in ISO 8601 format.
        public let earliestRestorableTimestamp: Date?
        /// Shows if point-in-time recovery is enabled or disabled for the specified table.
        public let status: PointInTimeRecoveryStatus

        public init(earliestRestorableTimestamp: Date? = nil, status: PointInTimeRecoveryStatus) {
            self.earliestRestorableTimestamp = earliestRestorableTimestamp
            self.status = status
        }

        private enum CodingKeys: String, CodingKey {
            case earliestRestorableTimestamp
            case status
        }
    }

    public struct RestoreTableRequest: AWSEncodableShape {
        /// Specifies the read/write throughput capacity mode for the target table. The options are: • throughputMode:PAY_PER_REQUEST  • throughputMode:PROVISIONED - Provisioned capacity mode requires readCapacityUnits and writeCapacityUnits as input. The default is throughput_mode:PAY_PER_REQUEST. For more information, see Read/write capacity modes in the Amazon Keyspaces Developer Guide.
        public let capacitySpecificationOverride: CapacitySpecification?
        /// Specifies the encryption settings for the target table. You can choose one of the following KMS key (KMS key): • type:AWS_OWNED_KMS_KEY - This key is owned by Amazon Keyspaces.  • type:CUSTOMER_MANAGED_KMS_KEY - This key is stored in your account and is created, owned, and managed by you.  This option  requires the kms_key_identifier of the KMS key in Amazon Resource Name (ARN) format as input.  The default is type:AWS_OWNED_KMS_KEY. For more information, see Encryption at rest in the Amazon Keyspaces Developer Guide.
        public let encryptionSpecificationOverride: EncryptionSpecification?
        /// Specifies the pointInTimeRecovery settings for the target table. The options are: • ENABLED   • DISABLED  If it's not specified, the default is DISABLED. For more information, see Point-in-time recovery in the Amazon Keyspaces Developer Guide.
        public let pointInTimeRecoveryOverride: PointInTimeRecovery?
        /// The restore timestamp in ISO 8601 format.
        public let restoreTimestamp: Date?
        /// The keyspace name of the source table.
        public let sourceKeyspaceName: String
        /// The name of the source table.
        public let sourceTableName: String
        /// A list of key-value pair tags to be attached to the restored table.  For more information, see Adding tags and labels to Amazon Keyspaces resources in the Amazon Keyspaces Developer Guide.
        public let tagsOverride: [Tag]?
        /// The name of the target keyspace.
        public let targetKeyspaceName: String
        /// The name of the target table.
        public let targetTableName: String

        public init(capacitySpecificationOverride: CapacitySpecification? = nil, encryptionSpecificationOverride: EncryptionSpecification? = nil, pointInTimeRecoveryOverride: PointInTimeRecovery? = nil, restoreTimestamp: Date? = nil, sourceKeyspaceName: String, sourceTableName: String, tagsOverride: [Tag]? = nil, targetKeyspaceName: String, targetTableName: String) {
            self.capacitySpecificationOverride = capacitySpecificationOverride
            self.encryptionSpecificationOverride = encryptionSpecificationOverride
            self.pointInTimeRecoveryOverride = pointInTimeRecoveryOverride
            self.restoreTimestamp = restoreTimestamp
            self.sourceKeyspaceName = sourceKeyspaceName
            self.sourceTableName = sourceTableName
            self.tagsOverride = tagsOverride
            self.targetKeyspaceName = targetKeyspaceName
            self.targetTableName = targetTableName
        }

        public func validate(name: String) throws {
            try self.capacitySpecificationOverride?.validate(name: "\(name).capacitySpecificationOverride")
            try self.encryptionSpecificationOverride?.validate(name: "\(name).encryptionSpecificationOverride")
            try self.validate(self.sourceKeyspaceName, name: "sourceKeyspaceName", parent: name, max: 48)
            try self.validate(self.sourceKeyspaceName, name: "sourceKeyspaceName", parent: name, min: 1)
            try self.validate(self.sourceKeyspaceName, name: "sourceKeyspaceName", parent: name, pattern: "^[a-zA-Z0-9][a-zA-Z0-9_]{1,47}$")
            try self.validate(self.sourceTableName, name: "sourceTableName", parent: name, max: 48)
            try self.validate(self.sourceTableName, name: "sourceTableName", parent: name, min: 1)
            try self.validate(self.sourceTableName, name: "sourceTableName", parent: name, pattern: "^[a-zA-Z0-9][a-zA-Z0-9_]{1,47}$")
            try self.tagsOverride?.forEach {
                try $0.validate(name: "\(name).tagsOverride[]")
            }
            try self.validate(self.tagsOverride, name: "tagsOverride", parent: name, max: 60)
            try self.validate(self.tagsOverride, name: "tagsOverride", parent: name, min: 1)
            try self.validate(self.targetKeyspaceName, name: "targetKeyspaceName", parent: name, max: 48)
            try self.validate(self.targetKeyspaceName, name: "targetKeyspaceName", parent: name, min: 1)
            try self.validate(self.targetKeyspaceName, name: "targetKeyspaceName", parent: name, pattern: "^[a-zA-Z0-9][a-zA-Z0-9_]{1,47}$")
            try self.validate(self.targetTableName, name: "targetTableName", parent: name, max: 48)
            try self.validate(self.targetTableName, name: "targetTableName", parent: name, min: 1)
            try self.validate(self.targetTableName, name: "targetTableName", parent: name, pattern: "^[a-zA-Z0-9][a-zA-Z0-9_]{1,47}$")
        }

        private enum CodingKeys: String, CodingKey {
            case capacitySpecificationOverride
            case encryptionSpecificationOverride
            case pointInTimeRecoveryOverride
            case restoreTimestamp
            case sourceKeyspaceName
            case sourceTableName
            case tagsOverride
            case targetKeyspaceName
            case targetTableName
        }
    }

    public struct RestoreTableResponse: AWSDecodableShape {
        /// The Amazon Resource Name (ARN) of the restored table.
        public let restoredTableARN: String

        public init(restoredTableARN: String) {
            self.restoredTableARN = restoredTableARN
        }

        private enum CodingKeys: String, CodingKey {
            case restoredTableARN
        }
    }

    public struct SchemaDefinition: AWSEncodableShape & AWSDecodableShape {
        /// The regular columns of the table.
        public let allColumns: [ColumnDefinition]
        /// The columns that are part of the clustering key of the table.
        public let clusteringKeys: [ClusteringKey]?
        /// The columns that are part of the partition key of the table .
        public let partitionKeys: [PartitionKey]
        /// The columns that have been defined as STATIC. Static columns store values that are shared by all rows in the same partition.
        public let staticColumns: [StaticColumn]?

        public init(allColumns: [ColumnDefinition], clusteringKeys: [ClusteringKey]? = nil, partitionKeys: [PartitionKey], staticColumns: [StaticColumn]? = nil) {
            self.allColumns = allColumns
            self.clusteringKeys = clusteringKeys
            self.partitionKeys = partitionKeys
            self.staticColumns = staticColumns
        }

        public func validate(name: String) throws {
            try self.validate(self.allColumns, name: "allColumns", parent: name, min: 1)
            try self.validate(self.partitionKeys, name: "partitionKeys", parent: name, min: 1)
        }

        private enum CodingKeys: String, CodingKey {
            case allColumns
            case clusteringKeys
            case partitionKeys
            case staticColumns
        }
    }

    public struct StaticColumn: AWSEncodableShape & AWSDecodableShape {
        /// The name of the static column.
        public let name: String

        public init(name: String) {
            self.name = name
        }

        private enum CodingKeys: String, CodingKey {
            case name
        }
    }

    public struct TableSummary: AWSDecodableShape {
        /// The name of the keyspace that the table is stored in.
        public let keyspaceName: String
        /// The unique identifier of the table in the format of an Amazon Resource Name (ARN).
        public let resourceArn: String
        /// The name of the table.
        public let tableName: String

        public init(keyspaceName: String, resourceArn: String, tableName: String) {
            self.keyspaceName = keyspaceName
            self.resourceArn = resourceArn
            self.tableName = tableName
        }

        private enum CodingKeys: String, CodingKey {
            case keyspaceName
            case resourceArn
            case tableName
        }
    }

    public struct Tag: AWSEncodableShape & AWSDecodableShape {
        /// The key of the tag. Tag keys are case sensitive. Each Amazon Keyspaces resource can only have up to one tag with the same key. If you try to add an  existing tag (same key), the existing tag value will be updated to the new value.
        public let key: String
        /// The value of the tag. Tag values are case-sensitive and can be null.
        public let value: String

        public init(key: String, value: String) {
            self.key = key
            self.value = value
        }

        public func validate(name: String) throws {
            try self.validate(self.key, name: "key", parent: name, max: 128)
            try self.validate(self.key, name: "key", parent: name, min: 1)
            try self.validate(self.value, name: "value", parent: name, max: 256)
            try self.validate(self.value, name: "value", parent: name, min: 1)
        }

        private enum CodingKeys: String, CodingKey {
            case key
            case value
        }
    }

    public struct TagResourceRequest: AWSEncodableShape {
        /// The Amazon Resource Name (ARN) of the Amazon Keyspaces resource to which to add tags.
        public let resourceArn: String
        /// The tags to be assigned to the Amazon Keyspaces resource.
        public let tags: [Tag]

        public init(resourceArn: String, tags: [Tag]) {
            self.resourceArn = resourceArn
            self.tags = tags
        }

        public func validate(name: String) throws {
            try self.validate(self.resourceArn, name: "resourceArn", parent: name, max: 1000)
            try self.validate(self.resourceArn, name: "resourceArn", parent: name, min: 20)
            try self.validate(self.resourceArn, name: "resourceArn", parent: name, pattern: "^arn:(aws[a-zA-Z0-9-]*):cassandra:.+")
            try self.tags.forEach {
                try $0.validate(name: "\(name).tags[]")
            }
            try self.validate(self.tags, name: "tags", parent: name, max: 60)
            try self.validate(self.tags, name: "tags", parent: name, min: 1)
        }

        private enum CodingKeys: String, CodingKey {
            case resourceArn
            case tags
        }
    }

    public struct TagResourceResponse: AWSDecodableShape {
        public init() {}
    }

    public struct TimeToLive: AWSEncodableShape & AWSDecodableShape {
        /// Shows how to enable custom Time to Live (TTL) settings for the specified table.
        public let status: TimeToLiveStatus

        public init(status: TimeToLiveStatus) {
            self.status = status
        }

        private enum CodingKeys: String, CodingKey {
            case status
        }
    }

    public struct UntagResourceRequest: AWSEncodableShape {
        /// The Amazon Keyspaces resource that the tags will be removed from. This value is an Amazon Resource Name (ARN).
        public let resourceArn: String
        /// A list of existing tags to be removed from the Amazon Keyspaces resource.
        public let tags: [Tag]

        public init(resourceArn: String, tags: [Tag]) {
            self.resourceArn = resourceArn
            self.tags = tags
        }

        public func validate(name: String) throws {
            try self.validate(self.resourceArn, name: "resourceArn", parent: name, max: 1000)
            try self.validate(self.resourceArn, name: "resourceArn", parent: name, min: 20)
            try self.validate(self.resourceArn, name: "resourceArn", parent: name, pattern: "^arn:(aws[a-zA-Z0-9-]*):cassandra:.+")
            try self.tags.forEach {
                try $0.validate(name: "\(name).tags[]")
            }
            try self.validate(self.tags, name: "tags", parent: name, max: 60)
            try self.validate(self.tags, name: "tags", parent: name, min: 1)
        }

        private enum CodingKeys: String, CodingKey {
            case resourceArn
            case tags
        }
    }

    public struct UntagResourceResponse: AWSDecodableShape {
        public init() {}
    }

    public struct UpdateTableRequest: AWSEncodableShape {
        /// For each column to be added to the specified table: • name  -  The name of the column. • type  -  An Amazon Keyspaces data type. For more information, see Data types in the Amazon Keyspaces Developer Guide.
        public let addColumns: [ColumnDefinition]?
        /// Modifies the read/write throughput capacity mode for the table. The options are: • throughputMode:PAY_PER_REQUEST and  • throughputMode:PROVISIONED - Provisioned capacity mode requires readCapacityUnits and writeCapacityUnits as input. The default is throughput_mode:PAY_PER_REQUEST. For more information, see Read/write capacity modes in the Amazon Keyspaces Developer Guide.
        public let capacitySpecification: CapacitySpecification?
        /// The default Time to Live setting in seconds for the table. For more information, see Setting the default TTL value for a table in the Amazon Keyspaces Developer Guide.
        public let defaultTimeToLive: Int?
        /// Modifies the encryption settings of the table. You can choose one of the following KMS key (KMS key): • type:AWS_OWNED_KMS_KEY - This key is owned by Amazon Keyspaces.  • type:CUSTOMER_MANAGED_KMS_KEY - This key is stored in your account and is created, owned, and managed by you.  This option  requires the kms_key_identifier of the KMS key in Amazon Resource Name (ARN) format as input.  The default is AWS_OWNED_KMS_KEY. For more information, see Encryption at rest in the Amazon Keyspaces Developer Guide.
        public let encryptionSpecification: EncryptionSpecification?
        /// The name of the keyspace the specified table is stored in.
        public let keyspaceName: String
        /// Modifies the pointInTimeRecovery settings of the table. The options are: • ENABLED   • DISABLED   If it's not specified, the default is DISABLED. For more information, see Point-in-time recovery in the Amazon Keyspaces Developer Guide.
        public let pointInTimeRecovery: PointInTimeRecovery?
        /// The name of the table.
        public let tableName: String
        /// Modifies Time to Live custom settings for the table. The options are: • status:enabled   • status:disabled   The default is status:disabled. After ttl is enabled, you can't disable it for the table. For more information, see Expiring data by using Amazon Keyspaces Time to Live (TTL) in the Amazon Keyspaces Developer Guide.
        public let ttl: TimeToLive?

        public init(addColumns: [ColumnDefinition]? = nil, capacitySpecification: CapacitySpecification? = nil, defaultTimeToLive: Int? = nil, encryptionSpecification: EncryptionSpecification? = nil, keyspaceName: String, pointInTimeRecovery: PointInTimeRecovery? = nil, tableName: String, ttl: TimeToLive? = nil) {
            self.addColumns = addColumns
            self.capacitySpecification = capacitySpecification
            self.defaultTimeToLive = defaultTimeToLive
            self.encryptionSpecification = encryptionSpecification
            self.keyspaceName = keyspaceName
            self.pointInTimeRecovery = pointInTimeRecovery
            self.tableName = tableName
            self.ttl = ttl
        }

        public func validate(name: String) throws {
            try self.validate(self.addColumns, name: "addColumns", parent: name, min: 1)
            try self.capacitySpecification?.validate(name: "\(name).capacitySpecification")
            try self.validate(self.defaultTimeToLive, name: "defaultTimeToLive", parent: name, max: 630_720_000)
            try self.validate(self.defaultTimeToLive, name: "defaultTimeToLive", parent: name, min: 1)
            try self.encryptionSpecification?.validate(name: "\(name).encryptionSpecification")
            try self.validate(self.keyspaceName, name: "keyspaceName", parent: name, max: 48)
            try self.validate(self.keyspaceName, name: "keyspaceName", parent: name, min: 1)
            try self.validate(self.keyspaceName, name: "keyspaceName", parent: name, pattern: "^[a-zA-Z0-9][a-zA-Z0-9_]{1,47}$")
            try self.validate(self.tableName, name: "tableName", parent: name, max: 48)
            try self.validate(self.tableName, name: "tableName", parent: name, min: 1)
            try self.validate(self.tableName, name: "tableName", parent: name, pattern: "^[a-zA-Z0-9][a-zA-Z0-9_]{1,47}$")
        }

        private enum CodingKeys: String, CodingKey {
            case addColumns
            case capacitySpecification
            case defaultTimeToLive
            case encryptionSpecification
            case keyspaceName
            case pointInTimeRecovery
            case tableName
            case ttl
        }
    }

    public struct UpdateTableResponse: AWSDecodableShape {
        /// The Amazon Resource Name (ARN) of the modified table.
        public let resourceArn: String

        public init(resourceArn: String) {
            self.resourceArn = resourceArn
        }

        private enum CodingKeys: String, CodingKey {
            case resourceArn
        }
    }
}

// MARK: - Errors

/// Error enum for Keyspaces
public struct KeyspacesErrorType: AWSErrorType {
    enum Code: String {
        case accessDeniedException = "AccessDeniedException"
        case conflictException = "ConflictException"
        case internalServerException = "InternalServerException"
        case resourceNotFoundException = "ResourceNotFoundException"
        case serviceQuotaExceededException = "ServiceQuotaExceededException"
        case validationException = "ValidationException"
    }

    private let error: Code
    public let context: AWSErrorContext?

    /// initialize Keyspaces
    public init?(errorCode: String, context: AWSErrorContext) {
        guard let error = Code(rawValue: errorCode) else { return nil }
        self.error = error
        self.context = context
    }

    internal init(_ error: Code) {
        self.error = error
        self.context = nil
    }

    /// return error code string
    public var errorCode: String { self.error.rawValue }

    /// You do not have sufficient access to perform this action.
    public static var accessDeniedException: Self { .init(.accessDeniedException) }
    /// Amazon Keyspaces could not complete the requested action. This error may occur if you try to  perform an action and the same or a different action is already in progress, or if you try to create a resource that already exists.
    public static var conflictException: Self { .init(.conflictException) }
    /// Amazon Keyspaces was unable to fully process this request because of an internal server error.
    public static var internalServerException: Self { .init(.internalServerException) }
    /// The operation tried to access a keyspace or table that doesn&#39;t exist. The resource might not be specified correctly, or its status might not be ACTIVE.
    public static var resourceNotFoundException: Self { .init(.resourceNotFoundException) }
    /// The operation exceeded the service quota for this resource.  For more information on service quotas, see Quotas in the Amazon Keyspaces Developer Guide.
    public static var serviceQuotaExceededException: Self { .init(.serviceQuotaExceededException) }
    /// The operation failed due to an invalid or malformed request.
    public static var validationException: Self { .init(.validationException) }
}

extension KeyspacesErrorType: Equatable {
    public static func == (lhs: KeyspacesErrorType, rhs: KeyspacesErrorType) -> Bool {
        lhs.error == rhs.error
    }
}

extension KeyspacesErrorType: CustomStringConvertible {
    public var description: String {
        return "\(self.error.rawValue): \(self.message ?? "")"
    }
}
